package com.yuyou.fn.analyze.service.impl;

import com.github.wens.framework.service.impl.SuperServiceImpl;
import com.github.wens.mybatisplus.examples.Example;
import com.github.wens.mybatisplus.plugins.Page;
import com.yuyou.fn.analyze.entity.ProductTarget;
import com.yuyou.fn.analyze.mapper.ProductTargetMapper;
import com.yuyou.fn.analyze.service.IProductTargetService;
import com.yuyou.fn.analyze.vo.ProductTargetResultVo;
import com.yuyou.fn.analyze.vo.ProductTargetVo;
import com.yuyou.fn.common.exception.BusException;
import com.yuyou.fn.common.util.BeanUtils;
import com.yuyou.fn.common.util.TimeUtils;
import com.yuyou.fn.common.util.Utils;
import com.yuyou.fn.educational.entity.Period;
import com.yuyou.fn.educational.entity.Product;
import com.yuyou.fn.educational.service.IPeriodService;
import com.yuyou.fn.educational.service.IProductService;
import com.yuyou.fn.educational.vo.ProductQueryVo;
import com.yuyou.fn.platform.permission.DataPermission;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.*;

/**
 *
 * ProductTarget 表数据服务层接口实现类
 *
 */
@Service
public class ProductTargetServiceImpl extends SuperServiceImpl<ProductTargetMapper, ProductTarget,Long> implements IProductTargetService {

    @Resource
    private IProductService productService;

    @Resource
    private IPeriodService periodService;



    @Override
    @Transactional
    public void insertByList(Long productId, String year, Integer targetType, List<ProductTargetVo> productTargetVoList) {
        this.deleteByProductId(productId,year,targetType);
        List<ProductTarget> productTargetList=new ArrayList<ProductTarget>();
        for (ProductTargetVo productTargetVo:productTargetVoList){
            ProductTarget productTarget=new ProductTarget();
            BeanUtils.copyProperties(productTarget,productTargetVo);
            productTarget.setCreateTime(TimeUtils.now());
            productTarget.setUpdateTime(TimeUtils.now());
            productTargetList.add(productTarget);
        }
        if (productTargetList.size()>0){
            this.insertBatch(productTargetList);
        }
    }

    @Override
    public void deleteByProductId(Long productId, String year, Integer targetType) {
        if(productId == null || year == null || targetType == null ){
            throw new NullPointerException();
        }
        Example example=ProductTarget.createExample();
        Example.Criteria criteria=example.createCriteria();
        criteria.andEqualTo("productId",productId);
        criteria.andEqualTo("year",year);
        criteria.andEqualTo("targetType",targetType);
        this.deleteByExample(example);
    }



    @Override
    public Page<ProductTargetResultVo> findPages(ProductQueryVo productQueryVo, DataPermission dataPermission, int pageNo, int pageSize, String year, Integer targetType) {
        if (productQueryVo.getAreaTeamId()==null){
            throw new BusException("必须选择一个区域");
        }
        List<Period> periodList=periodService.findByYearAndAreaTeamId(productQueryVo.getAreaTeamId(),year);
        List<Long> periodIdList=BeanUtils.toList(periodList,"periodId");
        if (periodIdList.size()<=0){
            throw new BusException("查不到期数请设置");
        }
        Page<Product> productPage=productService.findProductByQueryForUse(productQueryVo,dataPermission,pageNo,pageSize);
        Page<ProductTargetResultVo> productTargetResultVoPage=Utils.newPage(productPage);
        List<ProductTargetResultVo> productTargetResultVoList=new ArrayList<ProductTargetResultVo>();
        List<Product> productList=productPage.getRecords();

        Map<Long,String> productNameMap=new HashMap<Long,String>();
        if (productList!=null){
            for (Product product:productList){
                productNameMap.put(product.getProductId(),product.getName());
            }
        }



        if (productList!=null && productList.size()>0){
            List<Long> productIdList= BeanUtils.toList(productList,"productId");
            List<ProductTarget> productTargetList=findListByProductIdsAndPeriodIds(productIdList,periodIdList,year,targetType);
            Map<Long,List<ProductTarget>> map=BeanUtils.toGroup(productTargetList,"productId");
            List<ProductTarget> saveList=new ArrayList<ProductTarget>();
            for (Long productId:productIdList){
                if (map.containsKey(productId)){
                    List<ProductTarget> productTargets=map.get(productId);
                    List<Long> havePeriodIds=BeanUtils.toList(productTargets,"periodId");
                    for (Period period:periodList){
                        if (!havePeriodIds.contains(period.getPeriodId())){
                            ProductTarget productTarget=new ProductTarget();
                            productTarget.setProductId(productId);
                            productTarget.setYear(year);
                            productTarget.setTargetType(targetType);
                            productTarget.setCreateTime(TimeUtils.now());
                            productTarget.setUpdateTime(TimeUtils.now());
                            productTarget.setPeriodId(period.getPeriodId());
                            productTarget.setPeriodNo(period.getPeriodNo());
                            saveList.add(productTarget);
                        }
                    }
                }else {
                    for (Period period : periodList) {
                        ProductTarget productTarget = new ProductTarget();
                        productTarget.setProductId(productId);
                        productTarget.setYear(year);
                        productTarget.setTargetType(targetType);
                        productTarget.setCreateTime(TimeUtils.now());
                        productTarget.setUpdateTime(TimeUtils.now());
                        productTarget.setPeriodId(period.getPeriodId());
                        productTarget.setPeriodNo(period.getPeriodNo());
                        saveList.add(productTarget);
                    }
                }
            }
            if (saveList.size()>0){
                this.insertBatch(saveList);
            }
            List<ProductTarget> tempList=findListByProductIdsAndPeriodIds(productIdList,periodIdList,year,targetType);
            Map<Long,List<ProductTarget>> resultMap=BeanUtils.toGroup(tempList,"productId");
            Iterator<Map.Entry<Long, List<ProductTarget>>> entries = resultMap.entrySet().iterator();
            while (entries.hasNext()){
                ProductTargetResultVo productTargetResultVo=new ProductTargetResultVo();

                Map.Entry<Long, List<ProductTarget>> entry = entries.next();
                Long productId=entry.getKey();
                List<ProductTarget> productTargets=entry.getValue();
                productTargetResultVo.setProductId(productId);
                productTargetResultVo.setProductName(productNameMap.get(productId));
                productTargetResultVo.setTargetType(targetType);
                productTargetResultVo.setYear(year);
                productTargetResultVo.setProductTargetList(productTargets);
                productTargetResultVoList.add(productTargetResultVo);
            }
            productTargetResultVoPage.setRecords(productTargetResultVoList);
        }
        return productTargetResultVoPage;
    }



    @Override
    public List<ProductTarget> findListByProductIdsAndPeriodIds(List<Long> productIdList, List<Long> periodIds, String year, Integer targetType) {
        Example<ProductTarget> example=ProductTarget.createExample();
        Example.Criteria criteria=example.createCriteria();
        criteria.andIn("productId", productIdList);
        criteria.andIn("periodId",periodIds);
        if (StringUtils.isNotEmpty(year)){
            criteria.andEqualTo("year",year);
        }
        if (targetType !=null){
            criteria.andEqualTo("targetType", targetType);
        }
        example.orderBy("productId");
        example.orderBy("periodNo");
        return this.findListByExample(example);
    }
}